Skip to content

fix(ci): scope pip-audit to locked deps (was failing on transient runner pip CVE) - #53

Merged
Navi Bot (project-navi-bot) merged 1 commit into
mainfrom
fix/pip-audit-scope-to-locked-deps
Apr 26, 2026
Merged

fix(ci): scope pip-audit to locked deps (was failing on transient runner pip CVE)#53
Navi Bot (project-navi-bot) merged 1 commit into
mainfrom
fix/pip-audit-scope-to-locked-deps

Conversation

@Fieldnote-Echo

Copy link
Copy Markdown
Member

Summary

The security job in tests.yml is failing on every PR right now because uvx pip-audit==2.9.0 (with no -r argument) audits its own transient uvx environment, which contains the runner's pip 26.0.1 — flagged by GHSA-58qw-9mgm-455v / CVE-2026-3219 (pip tar/ZIP interpretation conflict, severity medium, no patched version available).

pip is not in our uv.lock — this audit was scanning the runner's Python environment, not our actual dependencies.

Fix

Export the resolved lockfile to a requirements file via uv export and pass it to pip-audit with -r. Audits exactly our pinned tree, ignores the transient uvx pip.

Stderr from uv export is redirected to /dev/null because it writes Resolved 36 packages in N ms which would otherwise land at line 1 of the requirements file under shell redirection and trip pip-audit's parser.

Test plan

Why this is the right fix (not just --ignore-vuln)

Adding --ignore-vuln GHSA-58qw-9mgm-455v would temporarily silence this specific advisory but leave the broader bug — auditing the runner's Python env instead of our project. When the next runner-image pip CVE drops we'd need another ignore. Scoping to our actual deps is the durable fix.

The security job was failing on every PR because `uvx pip-audit==2.9.0`
with no -r argument scans the transient uvx environment, which contains
its own pip 26.0.1 — flagged by GHSA-58qw-9mgm-455v / CVE-2026-3219
(pip tar/ZIP interpretation conflict, severity medium, no patched
version available yet). pip is not in our uv.lock; this audit was
auditing the runner's Python environment, not our actual deps.

Fix: export uv.lock to a requirements.txt and pass it via -r. Audits
exactly our pinned dependencies, ignores the transient runner pip.
Stderr is dropped because `uv export` writes 'Resolved 36 packages'
to stderr which would land at line 1 of the file via shell redirection
on some setups and trip pip-audit's parser.

Verified locally: 'No known vulnerabilities found' against current
uv.lock. Will keep working when upstream eventually patches pip; still
correctly fails CI if any of OUR pinned deps gain a new vuln.
Copilot AI review requested due to automatic review settings April 26, 2026 20:37
@qodo-code-review

Copy link
Copy Markdown

Review Summary by Qodo

Scope pip-audit to locked dependencies, fix runner CVE false positive

🐞 Bug fix

Grey Divider

Walkthroughs

Description
• Scope pip-audit to locked dependencies via uv export
• Prevents false positives from runner's transient pip environment
• Redirects uv export stderr to avoid parser issues
• Ensures audit only checks project's pinned dependencies
Diagram
flowchart LR
  A["uv.lock"] -->|"uv export"| B["requirements.txt"]
  B -->|"-r flag"| C["pip-audit 2.9.0"]
  C -->|"scans only"| D["Project dependencies"]
  E["Runner pip 26.0.1"] -.->|"ignored"| C
Loading

Grey Divider

File Changes

1. .github/workflows/tests.yml 🐞 Bug fix +8/-1

Scope pip-audit to locked dependencies via uv export

• Modified the Audit dependencies (pip-audit) step to export uv.lock to a requirements file
• Added uv export --format requirements.txt --no-emit-project --no-hashes command with stderr
 redirection
• Pass exported requirements file to pip-audit via -r flag instead of scanning transient
 environment
• Added explanatory comment documenting the CVE issue and fix rationale

.github/workflows/tests.yml


Grey Divider

Qodo Logo

@qodo-code-review

qodo-code-review Bot commented Apr 26, 2026

Copy link
Copy Markdown

Code Review by Qodo

🐞 Bugs (1) 📘 Rule violations (2)

Grey Divider


Action required

1. Disallowed .github/ path modified 📘 Rule violation § Compliance
Description
This PR modifies .github/workflows/tests.yml, which is outside the allowed top-level directories
(src/, tests/, packs/, docs/) and no explicit approval is recorded. This violates the
directory allow-list policy for file modifications.
Code

.github/workflows/tests.yml[R169-176]

+        # Scope the audit to OUR locked dependency tree exported from uv,
+        # not the transient uvx environment. Otherwise pip-audit also scans
+        # its own runtime (which currently flags the runner's pip 26.0.1
+        # for GHSA-58qw-9mgm-455v / CVE-2026-3219, an unpatched pip CVE
+        # that has nothing to do with this project's dependencies).
+        run: |
+          uv export --format requirements.txt --no-emit-project --no-hashes             > /tmp/audit-deps.txt 2>/dev/null
+          uvx pip-audit==2.9.0 -r /tmp/audit-deps.txt
Evidence
The checklist restricts changes to src/, tests/, packs/, or docs/ unless explicit approval
is recorded. The diff shows the only change is within .github/workflows/tests.yml, and the
provided PR description does not include an explicit approval note for modifying this disallowed
path.

Rule 305373: Restrict file modifications to specific top-level directories
.github/workflows/tests.yml[169-176]

Agent prompt
The issue below was found during a code review. Follow the provided context and guidance below and implement a solution

## Issue description
A file outside the allowed directory prefixes was modified without an explicit approval note.

## Issue Context
Policy allow-lists modifications to `src/`, `tests/`, `packs/`, `docs/` unless an explicit approval/exception is recorded in the PR.

## Fix Focus Areas
- .github/workflows/tests.yml[169-176]

ⓘ Copy this prompt and use it to remediate the issue with your preferred AI generation tools



Remediation recommended

2. tests.yml line too long 📘 Rule violation ✧ Quality
Description
A newly added workflow command line exceeds the 100-character limit. This reduces readability and
violates the source line-length requirement.
Code

.github/workflows/tests.yml[175]

+          uv export --format requirements.txt --no-emit-project --no-hashes             > /tmp/audit-deps.txt 2>/dev/null
Evidence
The checklist limits logical source lines to 100 characters. The added uv export ... command line
is significantly longer than 100 characters.

Rule 305371: Limit source lines to 100 characters
.github/workflows/tests.yml[175-175]

Agent prompt
The issue below was found during a code review. Follow the provided context and guidance below and implement a solution

## Issue description
A newly added command line in the workflow exceeds 100 characters.

## Issue Context
The repo enforces a 100-character line limit; long shell commands should be wrapped using `\` line continuations or split across multiple lines.

## Fix Focus Areas
- .github/workflows/tests.yml[175-175]

ⓘ Copy this prompt and use it to remediate the issue with your preferred AI generation tools


3. Export errors hidden 🐞 Bug ◔ Observability
Description
The security job redirects all uv export stderr to /dev/null, so if export fails the CI log
may not contain the root-cause diagnostics needed to fix it. This reduces observability and can turn
dependency-audit failures into opaque red/green debugging sessions.
Code

.github/workflows/tests.yml[175]

+          uv export --format requirements.txt --no-emit-project --no-hashes             > /tmp/audit-deps.txt 2>/dev/null
Evidence
The workflow discards stderr (2>/dev/null) for the uv export command, which is where most CLI
tools write warnings/errors, making failures harder to diagnose.

.github/workflows/tests.yml[168-176]

Agent prompt
The issue below was found during a code review. Follow the provided context and guidance below and implement a solution

### Issue description
The workflow discards all stderr from `uv export` (`2>/dev/null`). If `uv export` fails, the logs may not show the error details, making CI failures hard to debug.

### Issue Context
This is in the `security` job dependency audit step.

### Fix Focus Areas
- .github/workflows/tests.yml[168-176]

### Suggested change
Capture stderr to a temp file and only print it if `uv export` fails, e.g.:

```bash
uv export ... > /tmp/audit-deps.txt 2> /tmp/uv-export.stderr \
 || { cat /tmp/uv-export.stderr >&2; exit 1; }
uvx pip-audit==2.9.0 -r /tmp/audit-deps.txt
```

This keeps successful runs quiet (if desired) while preserving actionable error output on failure.

ⓘ Copy this prompt and use it to remediate the issue with your preferred AI generation tools


Grey Divider

Qodo Logo

@github-actions github-actions Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Grippy approves — PASS (100/100)

@github-actions

Copy link
Copy Markdown
Contributor

✅ Grippy Review — PASS

Score: 100/100 | Findings: 0


Commit: 62033e4

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Adjusts the CI dependency-audit step to scan only this repository’s locked dependencies (via uv.lock), avoiding false positives caused by vulnerabilities in the transient tool/runtime environment on GitHub-hosted runners.

Changes:

  • Export the resolved uv.lock dependency tree to a requirements file using uv export.
  • Run pip-audit against that exported requirements file (pip-audit -r ...) instead of auditing the transient uvx environment.

# for GHSA-58qw-9mgm-455v / CVE-2026-3219, an unpatched pip CVE
# that has nothing to do with this project's dependencies).
run: |
uv export --format requirements.txt --no-emit-project --no-hashes > /tmp/audit-deps.txt 2>/dev/null

Copilot AI Apr 26, 2026

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

uv export ... 2>/dev/null suppresses all stderr, which will hide real export errors/warnings and make CI failures much harder to debug (you'll just see a downstream pip-audit failure). Prefer keeping stderr visible, or suppress only the known benign progress line (e.g., via a --quiet/--no-progress flag if uv export supports it, or by filtering that specific line while still surfacing errors).

Suggested change
uv export --format requirements.txt --no-emit-project --no-hashes > /tmp/audit-deps.txt 2>/dev/null
uv export --format requirements.txt --no-emit-project --no-hashes > /tmp/audit-deps.txt

Copilot uses AI. Check for mistakes.
Comment on lines +169 to +176
# Scope the audit to OUR locked dependency tree exported from uv,
# not the transient uvx environment. Otherwise pip-audit also scans
# its own runtime (which currently flags the runner's pip 26.0.1
# for GHSA-58qw-9mgm-455v / CVE-2026-3219, an unpatched pip CVE
# that has nothing to do with this project's dependencies).
run: |
uv export --format requirements.txt --no-emit-project --no-hashes > /tmp/audit-deps.txt 2>/dev/null
uvx pip-audit==2.9.0 -r /tmp/audit-deps.txt

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Action required

1. Disallowed .github/ path modified 📘 Rule violation § Compliance

This PR modifies .github/workflows/tests.yml, which is outside the allowed top-level directories
(src/, tests/, packs/, docs/) and no explicit approval is recorded. This violates the
directory allow-list policy for file modifications.
Agent Prompt
## Issue description
A file outside the allowed directory prefixes was modified without an explicit approval note.

## Issue Context
Policy allow-lists modifications to `src/`, `tests/`, `packs/`, `docs/` unless an explicit approval/exception is recorded in the PR.

## Fix Focus Areas
- .github/workflows/tests.yml[169-176]

ⓘ Copy this prompt and use it to remediate the issue with your preferred AI generation tools

@project-navi-bot
Navi Bot (project-navi-bot) merged commit fa03198 into main Apr 26, 2026
19 checks passed
@project-navi-bot
Navi Bot (project-navi-bot) deleted the fix/pip-audit-scope-to-locked-deps branch April 26, 2026 23:46
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants